顶点坐标

opengl 顶点/纹理坐标

不使用buffer的顶点坐标

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
GLfloat quadVertexData [] = {
-1,-1,
-1,1,
1,1,
1,-1,
};

// Update attribute values.
glVertexAttribPointer(ATTRIB_VERTEX_LOC, 2, GL_FLOAT, 0, 0, quadVertexData);
glEnableVertexAttribArray(ATTRIB_VERTEX);


GLfloat quadTextureData[] = {
0, 0,
0, 1,
1, 1,
1, 0
};
glVertexAttribPointer(ATTRIB_TEXCOORD_LOC, 2, GL_FLOAT, 0, 0, quadTextureData);
glEnableVertexAttribArray(ATTRIB_TEXCOORD);

使用buffer的顶点坐标

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
// set up vertex data (and buffer(s)) and configure vertex attributes
// ------------------------------------------------------------------
float vertices[] = {
// positions // colors // texture coords
0.5f, 0.5f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, // top right
0.5f, -0.5f, 0.0f, 0.0f, 1.0f, 0.0f, 1.0f, 0.0f, // bottom right
-0.5f, -0.5f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, // bottom left
-0.5f, 0.5f, 0.0f, 1.0f, 1.0f, 0.0f, 0.0f, 1.0f // top left
};
unsigned int indices[] = {
0, 1, 3, // first triangle
1, 2, 3 // second triangle
};


glGenVertexArraysOES(1, &VAO);
glGenBuffers(1, &VBO);
glGenBuffers(1, &EBO);

glBindVertexArrayOES(VAO);

glBindBuffer(GL_ARRAY_BUFFER, VBO);
glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);

glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, EBO);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indices), indices, GL_STATIC_DRAW);

// position attribute
glVertexAttribPointer(_positionIndex, 3, GL_FLOAT, GL_FALSE, 8 * sizeof(float), (void*)0);
glEnableVertexAttribArray(_positionIndex);

// color attribute
glVertexAttribPointer(_colorIndex, 3, GL_FLOAT, GL_FALSE, 8 * sizeof(float), (void*)(3 * sizeof(float)));
glEnableVertexAttribArray(_colorIndex);

// texture coord attribute
glVertexAttribPointer(_textureIndex, 2, GL_FLOAT, GL_FALSE, 8 * sizeof(float), (void*)(6 * sizeof(float)));
glEnableVertexAttribArray(_textureIndex);

metal 顶点/纹理坐标

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
id<MTLBuffer> _vertexBuffer;
id <MTLDevice> _device;

···

float incubeVertexData[16] =
{
-1.0, -1.0, 0.0, 1.0,
1.0, -1.0, 1.0, 1.0,
-1.0, 1.0, 0.0, 0.0,
1.0, 1.0, 1.0, 0.0,
};

// Create a new command buffer for each renderpass to the current drawable
id <MTLCommandBuffer> commandBuffer = [_commandQueue commandBuffer];
commandBuffer.label = @"MyCommand";
id <MTLRenderCommandEncoder> renderEncoder = [commandBuffer renderCommandEncoderWithDescriptor:_renderPassDescriptor];

// Setup the vertex buffers
_vertexBuffer = [_device newBufferWithBytes:incubeVertexData length:sizeof(incubeVertexData) options:MTLResourceOptionCPUCacheModeDefault];
_vertexBuffer.label = @"Vertices";
[renderEncoder setVertexBuffer:_vertexBuffer offset:0 atIndex:0];

Shader

metal

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
#include <metal_stdlib>
#include <simd/simd.h>

using namespace metal;

typedef struct {
packed_float2 position;
packed_float2 texcoord;
} Vertex;

typedef struct {
float3x3 matrix;
float3 offset;
} ColorConversion;

typedef struct {
float4 position [[position]];
float2 texcoord;
} Varyings;

vertex Varyings vertexPassthrough(device Vertex* verticies [[ buffer(0) ]],unsigned int vid [[ vertex_id ]]) {
Varyings out;
device Vertex& v = verticies[vid];
out.position = float4(float2(v.position), 0.0, 1.0);
out.texcoord = v.texcoord;
return out;
}

fragment half4 fragmentColorConversion(
Varyings in [[ stage_in ]],
texture2d<float, access::sample> textureY [[ texture(0) ]],
texture2d<float, access::sample> textureCbCr [[ texture(1) ]],
constant ColorConversion &colorConversion [[ buffer(0) ]]
) {
constexpr sampler s(address::clamp_to_edge, filter::linear);
float3 ycbcr = float3(textureY.sample(s, in.texcoord).r, textureCbCr.sample(s, in.texcoord).rg);
float3 rgb = colorConversion.matrix * (ycbcr + colorConversion.offset);
return half4(half3(rgb), 1.0);
}

opengl

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
static const GLchar *shader_fsh = (const GLchar*)"varying highp vec2 texCoordVarying;"
"precision mediump float;"
"uniform sampler2D SamplerY;"
"uniform sampler2D SamplerUV;"
"uniform float rangeOffset;"
"uniform mat3 colorConversionMatrix;"
"void main()"
"{"
" mediump vec3 yuv;"
" lowp vec3 rgb;"
" yuv.x = (texture2D(SamplerY, texCoordVarying).r - (rangeOffset/255.0));"
" yuv.yz = (texture2D(SamplerUV, texCoordVarying).rg - vec2(0.5, 0.5));"
" rgb = colorConversionMatrix * yuv;"
" gl_FragColor = vec4(rgb, 1);"
"}";

static const GLchar *shader_vsh = (const GLchar*)"attribute vec4 position;"
"attribute vec2 texCoord;"
"uniform float preferredRotation;"
"varying vec2 texCoordVarying;"
"void main()"
"{"
" mat4 rotationMatrix = mat4(cos(preferredRotation), -sin(preferredRotation), 0.0, 0.0,"
" sin(preferredRotation), cos(preferredRotation), 0.0, 0.0,"
" 0.0, 0.0, 1.0, 0.0,"
" 0.0, 0.0, 0.0, 1.0);"
" gl_Position = position * rotationMatrix;"
" texCoordVarying = texCoord;"
"}";